using System;
using System.Windows.Forms;

namespace Widgetsphere.Generator.Common.GeneratorFramework
{
	public abstract class BaseModelObjectController : IModelObjectController
	{
		protected ModelObjectUserInterface _userInterface = null;
    protected IModelObject _object = null;
    protected ModelObjectTreeNode _node = null;

    #region Constructor

    public BaseModelObjectController(IModelObject modelObject)
    {			
      if (modelObject == null)
        throw new Exception("The model object cannot be null!");

      _object = modelObject;
      if (_object != null)
        ((BaseModelObject)this.Object).PropertyChanged += new System.ComponentModel.PropertyChangedEventHandler(ObjectPropertyChanged);

			modelObject.Controller = this;
    }

    #endregion

    #region Events

    public event ItemChanagedEventHandler ItemChanged;
		public void OnItemChanged(object sender, System.EventArgs e)
		{
			if(this.ItemChanged != null)
			{
				this.ItemChanged(sender, e);
			}
		}

		public event PropertyValueChangedEventHandler PropertyValueChanged;
		protected virtual void OnPropertyValueChanged(PropertyValueChangedEventArgs e)
		{
			if (this.PropertyValueChanged != null)
			{
				this.PropertyValueChanged(this, e);
			}
		}

		#endregion

    #region Property Implementations

    protected ModelObjectUserInterface UserInterface
    {
      get { return _userInterface; }
      set { _userInterface = value; }
    }

		protected bool _isEnabled = true;
		public virtual bool IsEnabled
		{
			get { return _isEnabled; }
		}

    #endregion

    #region IDisposable Members

    public void Dispose()
		{
			UIControl.Dispose();
		}

		#endregion

		#region UIControl

		public virtual ModelObjectUserInterface UIControl
		{
			get
			{
				if(this._userInterface == null)
				{
					Widgetsphere.Generator.Common.GeneratorFramework.PropertyGrid pg = new Widgetsphere.Generator.Common.GeneratorFramework.PropertyGrid();
					pg.SelectedObject = this.Object;
					pg.Dock = System.Windows.Forms.DockStyle.Fill;
					pg.PropertyValueChanged += new System.Windows.Forms.PropertyValueChangedEventHandler(pg_PropertyValueChanged);
					this._userInterface = pg;
				}
				this._userInterface.Enabled = this.IsEnabled;
				return this._userInterface;
			}
		}

		private void pg_PropertyValueChanged(object s, System.Windows.Forms.PropertyValueChangedEventArgs e)
		{
			this.OnPropertyValueChanged(e);
		}

		#endregion

    #region Verify

    public virtual MessageCollection Verify()
    {
      try
      {
        MessageCollection retval = new MessageCollection();
        foreach (ModelObjectTreeNode node in this.Node.Nodes)
          retval.AddRange(((BaseModelObjectController)node.Controller).Verify());
        return retval;
      }
      catch (Exception ex)
      {
        throw;
      }
    }

    #endregion

    #region Event Handlers

    protected virtual void ObjectPropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
    {
      this.OnItemChanged(this, new System.EventArgs());
    }

    #endregion

    public virtual IModelObject Object
    {
      get { return _object; }
    }

    public abstract ModelObjectTreeNode Node{get;}		
		public abstract MenuCommand[] GetMenuCommands();
    public abstract bool DeleteObject();
    public abstract void Refresh();

  }
}
